package br.lelu;

import java.util.ArrayList;
import java.util.Stack;

import android.app.Dialog;
import android.content.Context;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;

public class Compilador
{

	public static Context context;
	private TextView console;
	private String token = "";
	private int linha = 1, i = 0;
	static Integer[][] matriz = new Integer[73][44];
	static Integer tabelaRegras[][] = new Integer[66][11];
	static boolean verponto = false, verLiteral = false;
	static final String[] tokens = { "while", "var", "to", "then", "string",
		"real", "read", "program", "procedure", "print", "nreal", "nint",
		"literal", "integer", "if", "ident", "for", "end", "else", "do",
		"const", "begin", "vstring", ">=", ">", "=", "<>", "<=", "<", "+",
		";", ":=", ":", "/", ".", ",", "*", ")", "(", "{", "}", "-", "$",
		"�" };
	ArrayList<Tokens> fila = new ArrayList<Tokens>();
	private static Integer posicao;
	ArrayList<Variavel> variaveis = new ArrayList<Variavel>();
	ArrayList<Variavel> declaradas = new ArrayList<Variavel>();

	public Compilador(Context context, TextView console)
	{
		super();
		this.context = context;
		this.console = console;

		matriz[45][8] = 1;
		matriz[46][2] = 2;
		matriz[46][21] = 2;
		matriz[47][22] = 20;
		matriz[48][2] = 4;
		matriz[48][21] = 3;
		matriz[49][2] = 5;
		matriz[50][9] = 14;
		matriz[50][22] = 15;
		matriz[51][1] = 21;
		matriz[51][7] = 21;
		matriz[51][10] = 21;
		matriz[51][15] = 21;
		matriz[51][16] = 21;
		matriz[51][17] = 21;
		matriz[51][18] = 22;
		matriz[52][16] = 6;
		matriz[53][5] = 13;
		matriz[53][6] = 12;
		matriz[53][14] = 11;
		matriz[54][9] = 10;
		matriz[54][16] = 9;
		matriz[54][22] = 10;
		matriz[55][33] = 7;
		matriz[55][36] = 8;
		matriz[56][31] = 17;
		matriz[56][39] = 16;
		matriz[57][36] = 18;
		matriz[57][38] = 19;
		matriz[58][1] = 63;
		matriz[58][7] = 64;
		matriz[58][10] = 23;
		matriz[58][15] = 41;
		matriz[58][16] = 51;
		matriz[58][17] = 52;
		matriz[59][11] = 24;
		matriz[59][12] = 24;
		matriz[59][13] = 24;
		matriz[59][16] = 24;
		matriz[59][23] = 24;
		matriz[59][39] = 26;
		matriz[60][36] = 26;
		matriz[60][41] = 25;
		matriz[61][11] = 27;
		matriz[61][12] = 27;
		matriz[61][13] = 27;
		matriz[61][16] = 27;
		matriz[61][23] = 27;
		matriz[61][39] = 27;
		matriz[62][11] = 31;
		matriz[62][12] = 31;
		matriz[62][13] = 31;
		matriz[62][16] = 31;
		matriz[62][23] = 31;
		matriz[62][39] = 31;
		matriz[63][3] = 30;
		matriz[63][4] = 30;
		matriz[63][20] = 30;
		matriz[63][24] = 30;
		matriz[63][25] = 30;
		matriz[63][26] = 30;
		matriz[63][27] = 30;
		matriz[63][28] = 30;
		matriz[63][29] = 30;
		matriz[63][30] = 28;
		matriz[63][31] = 30;
		matriz[63][36] = 30;
		matriz[63][38] = 30;
		matriz[63][41] = 30;
		matriz[63][42] = 29;
		matriz[64][11] = 38;
		matriz[64][12] = 37;
		matriz[64][13] = 39;
		matriz[64][16] = 36;
		matriz[64][23] = 40;
		matriz[64][39] = 35;
		matriz[65][3] = 34;
		matriz[65][4] = 34;
		matriz[65][20] = 34;
		matriz[65][24] = 34;
		matriz[65][25] = 34;
		matriz[65][26] = 34;
		matriz[65][26] = 34;
		matriz[65][27] = 34;
		matriz[65][28] = 34;
		matriz[65][29] = 34;
		matriz[65][30] = 34;
		matriz[65][31] = 34;
		matriz[65][34] = 33;
		matriz[65][36] = 34;
		matriz[65][37] = 32;
		matriz[65][38] = 34;
		matriz[65][41] = 34;
		matriz[65][42] = 34;
		matriz[66][11] = 42;
		matriz[66][12] = 42;
		matriz[66][13] = 42;
		matriz[66][16] = 42;
		matriz[66][23] = 42;
		matriz[66][39] = 42;
		matriz[67][19] = 49;
		matriz[67][31] = 50;
		matriz[68][24] = 48;
		matriz[68][25] = 46;
		matriz[68][26] = 43;
		matriz[68][27] = 44;
		matriz[68][28] = 47;
		matriz[68][29] = 45;
		matriz[69][31] = 53;
		matriz[69][32] = 54;
		matriz[69][39] = 53;
		matriz[70][31] = 56;
		matriz[70][39] = 55;
		matriz[71][11] = 59;
		matriz[71][12] = 58;
		matriz[71][13] = 65;
		matriz[71][16] = 57;
		matriz[71][23] = 60;
		matriz[72][36] = 61;
		matriz[72][38] = 62;

		tabelaRegras[1][1] = 8;
		tabelaRegras[1][2] = 16;
		tabelaRegras[1][3] = 100;
		tabelaRegras[1][4] = 31;
		tabelaRegras[1][5] = 46;
		tabelaRegras[1][6] = 47;
		tabelaRegras[1][7] = 105;
		tabelaRegras[1][8] = 35;
		tabelaRegras[2][1] = 48;
		tabelaRegras[2][2] = 49;
		tabelaRegras[2][3] = 50;
		tabelaRegras[3][1] = 21;
		tabelaRegras[3][2] = 16;
		tabelaRegras[3][3] = 101;
		tabelaRegras[3][4] = 26;
		tabelaRegras[3][5] = 12;
		tabelaRegras[3][6] = 31;
		tabelaRegras[3][7] = 48;
		tabelaRegras[4][1] = 44;
		tabelaRegras[5][1] = 2;
		tabelaRegras[5][2] = 52;
		tabelaRegras[5][3] = 33;
		tabelaRegras[5][4] = 53;
		tabelaRegras[5][5] = 102;
		tabelaRegras[5][6] = 31;
		tabelaRegras[5][7] = 54;
		tabelaRegras[6][1] = 16;
		tabelaRegras[6][2] = 101;
		tabelaRegras[6][3] = 55;
		tabelaRegras[7][1] = 44;
		tabelaRegras[8][1] = 36;
		tabelaRegras[8][2] = 16;
		tabelaRegras[8][3] = 101;
		tabelaRegras[8][4] = 55;
		tabelaRegras[9][1] = 52;
		tabelaRegras[9][2] = 33;
		tabelaRegras[9][3] = 53;
		tabelaRegras[9][4] = 31;
		tabelaRegras[9][5] = 54;
		tabelaRegras[10][1] = 44;
		tabelaRegras[11][1] = 14;
		tabelaRegras[12][1] = 6;
		tabelaRegras[13][1] = 5;
		tabelaRegras[14][1] = 9;
		tabelaRegras[14][2] = 16;
		tabelaRegras[14][3] = 101;
		tabelaRegras[14][4] = 56;
		tabelaRegras[14][5] = 31;
		tabelaRegras[14][6] = 47;
		tabelaRegras[14][7] = 31;
		tabelaRegras[14][8] = 50;
		tabelaRegras[15][1] = 44;
		tabelaRegras[16][1] = 39;
		tabelaRegras[16][2] = 52;
		tabelaRegras[16][3] = 33;
		tabelaRegras[16][4] = 53;
		tabelaRegras[16][5] = 57;
		tabelaRegras[16][6] = 38;
		tabelaRegras[17][1] = 44;
		tabelaRegras[18][1] = 36;
		tabelaRegras[18][2] = 52;
		tabelaRegras[18][3] = 33;
		tabelaRegras[18][4] = 53;
		tabelaRegras[18][5] = 57;
		tabelaRegras[19][1] = 44;
		tabelaRegras[20][1] = 22;
		tabelaRegras[20][2] = 51;
		tabelaRegras[20][3] = 18;
		tabelaRegras[21][1] = 58;
		tabelaRegras[21][2] = 31;
		tabelaRegras[21][3] = 51;
		tabelaRegras[22][1] = 44;
		tabelaRegras[23][1] = 10;
		tabelaRegras[23][2] = 40;
		tabelaRegras[23][3] = 59;
		tabelaRegras[23][4] = 60;
		tabelaRegras[23][5] = 41;
		tabelaRegras[24][1] = 61;
		tabelaRegras[25][1] = 44;
		tabelaRegras[26][1] = 36;
		tabelaRegras[26][2] = 59;
		tabelaRegras[26][3] = 60;
		tabelaRegras[27][1] = 62;
		tabelaRegras[27][2] = 63;
		tabelaRegras[28][1] = 30;
		tabelaRegras[28][2] = 62;
		tabelaRegras[28][3] = 63;
		tabelaRegras[29][1] = 42;
		tabelaRegras[29][2] = 62;
		tabelaRegras[29][3] = 63;
		tabelaRegras[30][1] = 44;
		tabelaRegras[31][1] = 64;
		tabelaRegras[31][2] = 65;
		tabelaRegras[32][1] = 37;
		tabelaRegras[32][2] = 64;
		tabelaRegras[32][3] = 104;
		tabelaRegras[32][4] = 65;
		tabelaRegras[33][1] = 34;
		tabelaRegras[33][2] = 64;
		tabelaRegras[33][3] = 104;
		tabelaRegras[33][4] = 65;
		tabelaRegras[34][1] = 44;
		tabelaRegras[35][1] = 39;
		tabelaRegras[35][2] = 61;
		tabelaRegras[35][3] = 38;
		tabelaRegras[36][1] = 16;
		tabelaRegras[36][2] = 106;
		tabelaRegras[37][1] = 12;
		tabelaRegras[38][1] = 11;
		tabelaRegras[39][1] = 13;
		tabelaRegras[40][1] = 23;
		tabelaRegras[41][1] = 15;
		tabelaRegras[41][2] = 66;
		tabelaRegras[41][3] = 4;
		tabelaRegras[41][4] = 47;
		tabelaRegras[41][5] = 67;
		tabelaRegras[42][1] = 61;
		tabelaRegras[42][2] = 68;
		tabelaRegras[42][3] = 61;
		tabelaRegras[43][1] = 26;
		tabelaRegras[44][1] = 27;
		tabelaRegras[45][1] = 29;
		tabelaRegras[46][1] = 25;
		tabelaRegras[47][1] = 28;
		tabelaRegras[48][1] = 24;
		tabelaRegras[49][1] = 19;
		tabelaRegras[49][2] = 47;
		tabelaRegras[50][1] = 44;
		tabelaRegras[51][1] = 16;
		tabelaRegras[51][2] = 106;
		tabelaRegras[51][3] = 69;
		tabelaRegras[52][1] = 17;
		tabelaRegras[52][2] = 16;
		tabelaRegras[52][3] = 106;
		tabelaRegras[52][4] = 26;
		tabelaRegras[52][5] = 61;
		tabelaRegras[52][6] = 3;
		tabelaRegras[52][7] = 61;
		tabelaRegras[52][8] = 20;
		tabelaRegras[52][9] = 47;
		tabelaRegras[53][1] = 70;
		tabelaRegras[54][1] = 32;
		tabelaRegras[54][2] = 61;
		tabelaRegras[55][1] = 39;
		tabelaRegras[55][2] = 71;
		tabelaRegras[55][3] = 103;
		tabelaRegras[55][4] = 72;
		tabelaRegras[55][5] = 38;
		tabelaRegras[56][1] = 44;
		tabelaRegras[57][1] = 16;
		tabelaRegras[57][2] = 106;
		tabelaRegras[58][1] = 12;
		tabelaRegras[59][1] = 11;
		tabelaRegras[60][1] = 23;
		tabelaRegras[61][1] = 36;
		tabelaRegras[61][2] = 71;
		tabelaRegras[61][3] = 72;
		tabelaRegras[62][1] = 44;
		tabelaRegras[63][1] = 1;
		tabelaRegras[63][2] = 66;
		tabelaRegras[63][3] = 20;
		tabelaRegras[63][4] = 47;
		tabelaRegras[64][1] = 7;
		tabelaRegras[64][2] = 39;
		tabelaRegras[64][3] = 16;
		tabelaRegras[64][4] = 106;
		tabelaRegras[64][5] = 38;
		tabelaRegras[65][1] = 13;

	}

	public void compilar(String codigo)
	{
		posicao = 0;

		for (i = 0; i < codigo.length(); i++)
		{

			Character c = codigo.charAt(i);

			if (c.equals('\n') && c != null)
			{// if de quebra de linha
				linha++;
				this.token = "";
			}

			// ================================================================================================================================================================================

			if (c.equals(' ') && c != null)// if para pular espaço
				this.token = "";

			// ================================================================================================================================================================================

			if (c.equals('\t') && c != null)// if para pular tab
				this.token = "";

			// ================================================================================================================================================================================

			if ((c.equals('a') || c.equals('b') || c.equals('c')
				|| c.equals('d') || c.equals('e') || c.equals('f')
				|| c.equals('g') || c.equals('h') || c.equals('i')
				|| c.equals('j') || c.equals('k') || c.equals('l')
				|| c.equals('m') || c.equals('n') || c.equals('o')
				|| c.equals('p') || c.equals('q') || c.equals('r')
				|| c.equals('s') || c.equals('t') || c.equals('u')
				|| c.equals('v') || c.equals('y') || c.equals('x')
				|| c.equals('w') || c.equals('z'))
				&& c != null)
			{
				while (c.equals('a') || c.equals('b') || c.equals('c')
					   || c.equals('d') || c.equals('e') || c.equals('f')
					   || c.equals('g') || c.equals('h') || c.equals('i')
					   || c.equals('j') || c.equals('k') || c.equals('l')
					   || c.equals('m') || c.equals('n') || c.equals('o')
					   || c.equals('p') || c.equals('q') || c.equals('r')
					   || c.equals('s') || c.equals('t') || c.equals('u')
					   || c.equals('v') || c.equals('y') || c.equals('x')
					   || c.equals('w') || c.equals('z'))
				{
					this.token = this.token + c;
					// chama metodo para verificar se e
					// token
					if (verificaToken(this.token))
					{
						posicao++;
						this.token = "";
						break;
					}// fim da verificação de Token.
					else
					{
						i++;
						c = codigo.charAt(i);
					}
				}// fim do while de letras e numeros para token
				c = codigo.charAt(i);
			}// fim do if de letras para tokem

			// =================================================================================================================================================================================

			if ((c.equals('A') || c.equals('B') || c.equals('C')
				|| c.equals('D') || c.equals('E') || c.equals('F')
				|| c.equals('G') || c.equals('H') || c.equals('I')
				|| c.equals('J') || c.equals('K') || c.equals('L')
				|| c.equals('M') || c.equals('N') || c.equals('O')
				|| c.equals('P') || c.equals('Q') || c.equals('R')
				|| c.equals('S') || c.equals('T') || c.equals('U')
				|| c.equals('V') || c.equals('Y') || c.equals('X')
				|| c.equals('W') || c.equals('Z'))
				&& c != null)
			{
				while (c.equals('A') || c.equals('B') || c.equals('C')
					   || c.equals('D') || c.equals('E') || c.equals('F')
					   || c.equals('G') || c.equals('H') || c.equals('I')
					   || c.equals('J') || c.equals('K') || c.equals('L')
					   || c.equals('M') || c.equals('N') || c.equals('O')
					   || c.equals('P') || c.equals('Q') || c.equals('R')
					   || c.equals('S') || c.equals('T') || c.equals('U')
					   || c.equals('V') || c.equals('Y') || c.equals('X')
					   || c.equals('W') || c.equals('Z') || c.equals('0')
					   || c.equals('1') || c.equals('2') || c.equals('3')
					   || c.equals('4') || c.equals('5') || c.equals('6')
					   || c.equals('7') || c.equals('8') || c.equals('9')
					   || c.equals('_'))
				{
					this.token = this.token + c;
					i++;
					c = codigo.charAt(i);
				}// fim do while de letras e numeros para token

				fila.add(new Tokens(16, linha, posicao));
				variaveis.add(new Variavel(token, posicao, null));
				posicao++;
				console.setText(console.getText().toString() + "\n"
								+ "Código: 16		|	linha: " + linha + "		|	Token: ident");// escreve
				// no
				// console
				Log.i("TOKEM", "Código: 15 Token: ident linha: " + linha);
				this.token = "";
				c = codigo.charAt(i);
			}// fim do if de letras para tokem

			// ==================================================================================================================================================================================

			if ((c.equals('0') || c.equals('1') || c.equals('2')
				|| c.equals('3') || c.equals('4') || c.equals('5')
				|| c.equals('6') || c.equals('7') || c.equals('8') || c
				.equals('9')) && c != null)
			{
				verponto = false;
				while (c.equals('0') || c.equals('1') || c.equals('2')
					   || c.equals('3') || c.equals('4') || c.equals('5')
					   || c.equals('6') || c.equals('7') || c.equals('8')
					   || c.equals('9') || c.equals('.'))
				{

					if (c.equals('.') && verponto == false)
					{
						verponto = true;
					}
					else
					{
						if (c.equals('.') && verponto == true)
						{
							i = codigo.length();
							this.token = "";
							c = null;
							menssagemErro("Número real escrito incorreto");
							Log.i("TOKEN", token + " erro real");
							Log.i("TOKEN", c + " exibe valor do c");
							break;
						}
					}

					this.token += c;
					i++;
					c = codigo.charAt(i);
					Log.i("TOKEN", token);
				}// fim do while de numero
				if (verificaTokennum(this.token))
				{
					posicao++;
					Log.i("TOKEN", token + "Verifica numero");
					this.token = "";
				}// fim da verificação de Token.
				c = codigo.charAt(i);
			}// fim do if de numero

			// ================================================================================================================================================================================

			if (c.equals('>') && c != null)
			{
				token += c;

				if (codigo.charAt(i + 1) == '=')
				{
					i++;
					token += codigo.charAt(i);
					verificaToken(token);
					posicao++;
				}
				else
				{
					verificaToken(token);
					posicao++;
				}
				this.token = "";
			}

			// ================================================================================================================================================================================

			if (c.equals('<') && c != null)
			{
				token += c;

				if (codigo.charAt(i + 1) == '=')
				{
					i++;
					token += codigo.charAt(i);
					verificaToken(token);
					posicao++;
				}
				else if (codigo.charAt(i + 1) == '>')
				{
					i++;
					token += codigo.charAt(i);
					verificaToken(token);
					posicao++;
				}
				else
				{
					verificaToken(token);
					posicao++;
				}
				this.token = "";
			}

			// ================================================================================================================================================================================

			if (c.equals('"') && c != null)
			{

				boolean erro = true;
				Log.i("TOKEM", String.valueOf(verLiteral));

				if (verLiteral)
				{
					verLiteral = false;
					i++;
					do {
						c = codigo.charAt(i);
						if (c.equals('\n'))
						{

							menssagemErro("Literal da  linha " + linha
										  + " não finalizado");

							console.setText(console.getText().toString() + "\n"
											+ "Literal da  linha " + linha
											+ " não finalizado");// escreve no console
							i = codigo.length();
							erro = false;
							break;
						}
						else
						{
							i++;
						}
					} while (!c.equals('"'));

					if (erro)
					{
						fila.add(new Tokens(13, linha, posicao));
						posicao++;
						console.setText(console.getText().toString() + "\n"
										+ "Código: 13		|	linha: " + linha
										+ "		|	Token: literal");// escreve no console
						Log.i("TOKEM", "Código: 13 Token: literal linha: "
							  + linha);// escreve
						// no
						// LogCat
					}
				}
				else
				{
					do {
						if (codigo.charAt(i) == '\n')
						{

							menssagemErro("vString da  linha " + linha
										  + " não finalizado");

							console.setText(console.getText().toString() + "\n"
											+ "vString da  linha " + linha
											+ " não finalizado");// escreve no console
							i = codigo.length();
							erro = false;
							break;
						}
						else
						{
							i++;
						}
					} while (codigo.charAt(i) != '"');
					// while(codigo.charAt(i)!='"'){
					// i++;
					// }
					if (erro)
					{
						fila.add(new Tokens(23, linha, posicao));
						posicao++;
						console.setText(console.getText().toString() + "\n"
										+ "Código: 23		|	linha: " + linha
										+ "		|	Token: vstring");// escreve no console
						Log.i("TOKEM", "Código: 23 Token: vstring linha: "
							  + linha);// escreve
						// no
						// LogCat
					}
				}
				token = "";
				c = codigo.charAt(i);
			}

			// ================================================================================================================================================================================

			if (c.equals('[') && c != null)
			{
				int linhaAux = linha;
				do {

					if ((i + 1) == codigo.length())
					{
						menssagemErro("Comentário da  linha " + linhaAux
									  + " não finalizado");
						console.setText(console.getText().toString() + "\n"
										+ "Comentário da  linha " + linhaAux
										+ " não finalizado");// escreve no console
						break;
					}
					else
						i++;
					c = codigo.charAt(i);
					if (c.equals('\n'))
					{
						linha++;
					}
				} while (codigo.charAt(i) != ']');
				c = codigo.charAt(i);
			}

			// ================================================================================================================================================================================

			if ((c.equals('+') || c.equals('-') || c.equals('*')
				|| c.equals('(') || c.equals(')') || c.equals('{')
				|| c.equals('}') || c.equals('/') || c.equals('.')
				|| c.equals(',') || c.equals('=') || c.equals(';'))
				&& c != null)
			{
				token += c;
				verificaToken(token);
				posicao++;
				token = "";
			}

			// ================================================================================================================================================================================

			if (c.equals(':') && c != null)
			{
				token += c;

				if (codigo.charAt(i + 1) == '=')
				{
					i++;
					token += codigo.charAt(i);
					verificaToken(token);
					posicao++;
				}
				else
				{
					verificaToken(token);
					posicao++;
				}

				this.token = "";
			}

			// ================================================================================================================================================================================

			if (c.equals('|') && c != null)
			{
				token += c;

				if (codigo.charAt(i + 1) == '|')
				{
					while (!c.equals('\n'))
					{
						i++;
						c = codigo.charAt(i);
					}
				}
				else
				{
					menssagemErro("Comentário de linha iniciado incorretamente");
					i = codigo.length();
				}

				this.token = "";
			}

			// =================================================================================================================================================================================

			if ((i + 1) >= codigo.length())
			{
				fila.add(new Tokens(43, linha, posicao));
				posicao++;
				console.setText(console.getText().toString() + "\n"
								+ "Código: 43		|	linha: " + linha + "		|	Token: $");// escreve
				// no
				// console
				Log.i("TOKEM", "Código: 43 Token: $ linha: " + linha);
				break;
			}

		}// fim do for de leitura

		if (analisadorSintatico())
		{
			menssagemErro("Programa sem erros");
		}

	}

	public boolean verificaToken(String s)
	{
		// Log.i("TOKEM", s);
		if (s.equals("print"))
		{
			verLiteral = true;
		}
		Log.w("COMPILADOR", "Token: " + s);
		for (int i = 0; i < 44; i++)
		{
			// for para verificar se a string passada e um token
			if (tokens[i].compareTo(s) == 0)
			{// se for token vai escrever no
				// TexteView console e no LogCat
				// o código a linha e o token
				fila.add(new Tokens((i + 1), linha, posicao));
				console.setText(console.getText().toString() + "\n"
								+ "Código: " + (i + 1) + "		|	linha: " + linha
								+ "		|	Token: " + tokens[i]);// escreve no console
				Log.i("TOKEM", "Código: " + (i + 1) + " Token: " + tokens[i]
					  + " linha: " + linha);// escreve no LogCat

				return true;
			}
		}
		return false;
	}

	public boolean verificaTokennum(String s)
	{
		String valor = s;
		if (verponto == true)
		{
			s = "nreal";
		}
		else
		{
			if (verponto == false)
			{
				s = "nint";
			}
		}
		for (int i = 0; i < 40; i++)
		// for para verificar se a string passada e um token
			if (tokens[i].compareTo(s) == 0)
			{// se for token vai escrever no
				// TexteView console e no LogCat
				// o código a linha e o token
				if (s.equals("nreal"))
				{
					fila.add(new Tokens((i + 1), linha, posicao));
					variaveis.add(new Variavel(posicao, 'R', valor));
				}
				else
				{
					fila.add(new Tokens((i + 1), linha, posicao));
					variaveis.add(new Variavel(posicao, 'I', valor));
				}
				console.setText(console.getText().toString() + "\n"
								+ "Código: " + (i + 1) + "		|	linha: " + linha
								+ "		|	Token: " + tokens[i]);// escreve no console
				Log.i("TOKEM", "Código: " + (i + 1) + " Token: " + tokens[i]
					  + " linha: " + linha);// escreve no LogCat
				return true;
			}
		return false;
	}

	public boolean analisadorSintatico()
	{


		for (int i = 0; i < variaveis.size(); i++)
		{
			Log.i("SEMANTICO", "Nome variavel: " + variaveis.get(i).getNome() + " Valor: " + variaveis.get(i).getValor());
		}

		Stack<Integer> pilha = new Stack<Integer>();
		Log.i("SINTATICO", "Iniciada Analise Sintatica");

		boolean verifica = true;

		pilha.push(43);
		pilha.push(45);

		Integer x, a, contador = 0;

		do {
			x = pilha.peek();
			a = fila.get(contador).getToken();
			if (x.equals(44))
			{
				Log.e("SINTATICO", "Remove vazio do topo da pilha");
				pilha.pop();
				x = pilha.peek();
			}
			else if (1 <= x && x <= 44)
			{
				Log.e("SINTATICO", "Pilha: " + x + " Fila: " + a);
				Log.i("SINTATICO", "Token: " + tokens[a - 1]);
				if (x.equals(a))
				{

					pilha.pop();
					if (!pilha.empty())
					{
						x = pilha.peek();
					}
					else
					{
						x = null;
					}
					contador++;
				}
				else
				{
					menssagemErro(context
								  .getString(R.string.erro_sintatico_linha)
								  + (fila.get(contador).getLinha()));
					verifica = false;
					break;
				}
			}
			else
			{
				if (x >= 100)
				{

					Log.e("SEMANTICO", "Semantico inicio cont: " + contador);
					if (!analisadorSemantico(x, fila.get(contador - 1), contador - 1))
					{
						verifica = false;
					}
					Log.e("SEMANTICO", "Semantico fim cont: " + contador);

					pilha.pop();
					if (!pilha.empty())
					{
						x = pilha.peek();
					}
					else
					{
						x = null;
					}
				}
				else
				{
					Log.e("SINTATICO", "Pilha: " + x + " Fila: " + a);
					if (matriz[x][a] != null)
					{
						int regra = matriz[x][a];
						Log.e("SINTATICO", "Regra: " + regra);
						pilha.pop();
						for (int index = 9; index >= 0; index--)
						{
							if (tabelaRegras[regra][index] != null)
							{
								pilha.push(tabelaRegras[regra][index]);
								Log.e("SINTATICO", "Add pilha: " + pilha.peek());
							}
							x = pilha.peek();
						}
					}
					else
					{
						menssagemErro(context
									  .getString(R.string.erro_sintatico_linha)
									  + (fila.get(contador).getLinha() - 1));
						verifica = false;
						break;
					}
				}
			}
		} while (!pilha.empty() && x != null);

		return verifica;
	}

	public boolean analisadorSemantico(int acao, Tokens t, int p)
	{
		boolean teste = true;
		switch (acao)
		{
			case 100: {
					Log.e("SEMANTICO", "Samantico 100");
					for (int j = 0; j < variaveis.size();j++)
					{
						if (variaveis.get(j).getPosicao() == p)
						{
							Log.i("SEMANTICO", "Nome Programa: " + variaveis.get(j).getNome());
							declaradas.add(new Variavel(variaveis.get(j).getNome(), variaveis.get(j).getPosicao(), 'N'));					
						}
					}

					return true;			
				}
			case 101: {
					Log.e("SEMANTICO", "Semantico 101 + variaveis posicao: " + t.getPosicao() + " posicao: " + p);
					int contVaravel = 0;
					for (int i = 0; i < variaveis.size(); i++)
					{
//				Log.e("SEMANTICO", "Semantico 101 + variaveis nome: "+variaveis.get(i).getNome()+ " posicao: "+variaveis.get(i).getPosicao()+" fila: "+p);
						if (variaveis.get(i).getPosicao() == p)
						{
							Log.i("SEMANTICO", "Nome variavel: " + variaveis.get(i).getNome());
							declaradas.add(new Variavel(variaveis.get(i).getNome(), variaveis.get(i).getPosicao(), null));							
							for (int j = i; j >= 0;j--)
							{
								if (variaveis.get(i).getNome().equals(variaveis.get(j).getNome()))
								{
									contVaravel++;		
								}
							}				
						}
					}
					if (contVaravel > 1)
					{
						menssagemErro("Erro Semantico nome de variavel repitido");
						return false;
					}
					else
					{
						return true;
					}
				}
			case 102: {
					Log.e("SEMANTICO", "Semantico 102");
					for (int i=p; i > 0;i--)
					{
						if (fila.get(i).getToken() != 2 || fila.get(i).getToken() != 5 || fila.get(i).getToken() != 6 || fila.get(i).getToken() != 14)
						{
							if (fila.get(i).getToken() == 16)
							{
								for (int j = 0; j < variaveis.size();j++)
								{
									if (variaveis.get(j).getPosicao() == i)
									{
										Log.e("SEMANTICO", "Samantico 102 fila: " + i + " variaveis: " + variaveis.get(j).getPosicao());
										switch (fila.get(p).getToken())
										{
											case 5:									
												variaveis.get(j).setTipo('S');
												break;
											case 6:
												variaveis.get(j).setTipo('R');
												break;
											case 14:
												variaveis.get(j).setTipo('I');
												break;
											default:
												break;
										}
									}
								}

							}
						}
						else
						{
							break;
						}
					}
					for (int i=0; i < declaradas.size();i++)
					{						
						Log.d("SEMANTICO","Variavel: " + declaradas.get(i).getNome() +" Tipo: "+declaradas.get(i).getTipo());
					}
					
					return true;		
				}
//			case 104:{
//				for(int i=0; i<variaveis.size();i++){
//					if(variaveis.get(i).getPosicao()==p){
//						if(variaveis.get(i+1).getTipo()=='R'){
//							if(Double.valueOf(variaveis.get(i+1).getValor())==0){
//								menssagemErro("Divisãop");
//							}
//						}
//					}
//				}
//			}	
			case 105:{
					for (int i=0; i < declaradas.size();i++)
					{						
						Log.d("SEMANTICO","Variavel: " + declaradas.get(i).getNome() );
						}
					Log.e("SEMANTICO", "Semantico 105");
					for (int i=0; i < variaveis.size();i++)
					{
						for (int j=0; j < declaradas.size();j++)
						{
							if(variaveis.get(i).getNome()!=null){
								if (variaveis.get(i).getNome().equals(declaradas.get(j).getNome()))
								{
									declaradas.get(j).contador();
								}}
							
						}
					}
					for (int i=1; i < declaradas.size();i++)
					{
						if (declaradas.get(i).getCont() < 2)
						{
							menssagemErro("Variavel: " + declaradas.get(i).getNome() + " não utilizada");
						}
					}
					return true;
				}
				case 106:{

						Log.e("SEMANTICO", "Semantico 106");
					boolean verifica=false;
					Variavel v = null;
					for(int i=0; i<variaveis.size();i++){
						if(p==variaveis.get(i).getPosicao()){
							v=variaveis.get(i);
							break;
						}
					}
					
					for(int i=0; i<declaradas.size();i++){
						if(v.getNome().equals(declaradas.get(i).getNome())){
							verifica=true;
						}
					}					
					if(!verifica){
						menssagemErro("Variavel "+v.getNome()+" não declarada");
					}
					return verifica;
				}
			default:
				return true;
		}
	}

	/***** Metodo que exibe menssagem de erro passando String por parametro ******/
	public void menssagemErro(String msg)
	{

		final Dialog d = new Dialog(context);
		d.setContentView(R.layout.erro);
		d.setTitle(R.string.titulo_aviso);
		final TextView edit = (TextView) d.findViewById(R.id.tvErro);
		final Button bt = (Button) d.findViewById(R.id.btErro);
		edit.setText(msg);
		bt.setOnClickListener(new OnClickListener() {

				public void onClick(View v)
				{
					// TODO Auto-generated method stub
					d.dismiss();
				}
			});
		d.show();
	}

	/******
	 * Metodo que exibe menssagem de erro passando id de
	 * String(R.string.nome_string) por parametro
	 ******/
	public void menssagemErro(int id)
	{

		final Dialog d = new Dialog(context);
		d.setContentView(R.layout.erro);
		d.setTitle(R.string.titulo_aviso);
		final TextView edit = (TextView) d.findViewById(R.id.tvErro);
		final Button bt = (Button) d.findViewById(R.id.btErro);
		edit.setText(id);
		bt.setOnClickListener(new OnClickListener() {

				public void onClick(View v)
				{
					// TODO Auto-generated method stub
					d.dismiss();
				}
			});
		d.show();
	}

}
